﻿using System.Collections.Generic;

namespace Sidvall.UI.ViewModels
{
    public class ViewModelControlCollection : System.Collections.ObjectModel.Collection<ControlViewModelBase>
    {
        #region Public Members

        public event System.EventHandler<Sidvall.UI.Messaging.BusyChangedEventArgs> IsBusyChanged;

        #region AddRange

        public void AddRange(IEnumerable<ControlViewModelBase> items)
        {
            if (items == null)
                return;
            foreach (var item in items)
                Add(item);
        }

        #endregion
        #region ClearItems

        protected override void ClearItems()
        {
            foreach (var item in this)
                DeleteItem(item);
            base.ClearItems();
        }

        #endregion
        #region GetItem

        public ControlViewModelBase GetItem(int index)
        {
            if (index == int.MaxValue)
                return null;
            if (this.Count < index + 1)
                return null;
            return this[index];
        }

        #endregion
        #region InsertItem

        protected override void InsertItem(int index, ControlViewModelBase item)
        {
            base.InsertItem(index, item);
            AddEventHooks(item);
        }

        #endregion
        #region RemoveItem

        protected override void RemoveItem(int index)
        {
            var item = this[index];
            DeleteItem(item);
            base.RemoveItem(index);
        }

        #endregion
        #region SetItem

        protected override void SetItem(int index, ControlViewModelBase item)
        {
            var child = this[index];
            if (!ReferenceEquals(child, item))
                DeleteItem(child);
            base.SetItem(index, item);
            AddEventHooks(item);
        }

        #endregion
        #region SetItemByForce

        public void SetItemByForce(int index, ControlViewModelBase item)
        {
            if (this.Count < index + 1)
            {
                while (this.Count < index)
                    Add(null);
                Add(item);
            }
            else
            {
                this[index] = item;
            }
        }

        #endregion

        #region OnIsBusyChanged

        public void OnIsBusyChanged(object sender, Sidvall.UI.Messaging.BusyChangedEventArgs e)
        {
            if (this.IsBusyChanged != null)
                this.IsBusyChanged(sender, e);
        }

        #endregion

        #endregion
        #region Private Members

        #region AddEventHooks

        private void AddEventHooks(ControlViewModelBase item)
        {
            if (item == null)
                return;
            item.IsBusyChanged += OnIsBusyChanged;
        }

        #endregion
        #region DeleteItem

        private void DeleteItem(ControlViewModelBase item)
        {
            if (item == null)
                return;
            RemoveEventHooks(item);
            item.Dispose();
        }

        #endregion
        #region RemoveEventHooks

        private void RemoveEventHooks(ControlViewModelBase item)
        {
            if (item == null)
                return;
            item.IsBusyChanged -= OnIsBusyChanged;
        }

        #endregion

        #endregion
    }
}
